
;shop routines

;populates shop_topcards_template
shop_load_topcard_template:
	;red template (30 tiles)
	ld		hl,shop_red_card
	ld		de,graphics_buffer
	call	unpack
	
	ld		hl,graphics_buffer
	ld		de,shop_topcards_template
	ld		bc,30
	ldir

	;blue template (30 tiles)
	ld		hl,shop_blue_card
	ld		de,graphics_buffer
	call	unpack
	
	ld		hl,graphics_buffer
	ld		de,shop_topcards_template+30
	ld		bc,30
	ldir

	;green template (30 tiles)
	ld		hl,shop_green_card
	ld		de,graphics_buffer
	call	unpack
	
	ld		hl,graphics_buffer
	ld		de,shop_topcards_template+60
	ld		bc,30
	ldir


	ret


;copies from rom deck status to ram
init_player_deck_status:
	ld		b,MAX_CARDS_GAME+1
	
	ld		hl,cards_regs+1					;pointing at first card flag
	ld		de,player_deck_status
	
init_player_deck_status_loop:
	push	bc
	ld		a,[hl]
	and		11000000b
	ld		[de],a							;TODO: check if I can use LDI

	ld		b,0
	ld		c,CARD_REG_SIZE					;TODO: can I optimize this bit?

	add		hl,bc


	inc		de
	pop		bc	
	djnz	init_player_deck_status_loop


	ret


;inits cards owned and cards in deck vars
;destroys all basic regs
shop_init_counters:
	xor		a
	ld		[shop_cards_in_deck],a
	ld		[shop_cards_owned],a
	
	ld		b,MAX_CARDS_GAME+1
	ld		hl,player_deck_status

shop_init_counters_loop:	
	ld		a,[hl]
	bit		7,a
	jr		z,shop_init_counters_dont_add_indeck
	push	af
	ld		a,[shop_cards_in_deck]
	inc		a
	ld		[shop_cards_in_deck],a
	pop		af
shop_init_counters_dont_add_indeck:
	bit		6,a
	jr		z,shop_init_counters_dont_add_owned
	ld		a,[shop_cards_owned]
	inc		a
	ld		[shop_cards_owned],a
shop_init_counters_dont_add_owned:	
	inc		hl
	djnz	shop_init_counters_loop

	ret



shop_update_flashing_flags_counter
	ld		a,[shop_flashing_flags_counter]
	ld		b,a									;saved a for later use
	and		01111111b
	dec		a	
	jr		z,shop_update_flashing_flags_counter_change
	push	af
	ld		a,b
	and		10000000b
	ld		b,a
	pop		af
	or		b
	ld		[shop_flashing_flags_counter],a
	
	ret

shop_update_flashing_flags_counter_change:
	ld		a,[shop_flashing_flags_counter]
	and		10000000b
	cpl					;flip flag
	and		10000000b
	ld		b,5
	or		b
	ld		[shop_flashing_flags_counter],a

	ret

	
	
shop_main_loop:
;Following Jon Cortazar advices 
	
	call	shop_keyboard_polling
	
	call	shop_update_flashing_flags_counter
	
	call	update_shop_fires_fx
	
	halt
	
	call	display_update_shop
	
	call	display_shop_fires_fx
	

	IF DEBUG_MODE==1
	ld		a,[shop_card_list+3]

	ld		h,0
	ld		l,a
	ld		de,debug_buffer1

	call	Num2Dec
	
	ld		hl,debug_buffer1
	ld		de,NAMTBL+28
	ld		bc,3
	call	0x005c
	
	ENDIF	
	
	;call	REPRODUCE_EFECTO

	jr		shop_main_loop


	ret

	
	
	
;this routine must be called after shop_move_filter_right or shop_move_filter_left
;modifies all basic registers
shop_filter_leftright_common_code:

	;prints filter in memory
	call	print_filter

	ld		a,[shop_filter]
	and		a
	jr		z,shop_filter_leftright_common_code_all
	;populate shop card list depending on the color
	ld		a,[shop_filter]								;TODO: probably I don't need to do it ... a is not destroyed by and a
	call	search_firstcard_by_color					;a contains the card number on return
	ld		b,1
	jr		shop_filter_leftright_common_code_color
	
shop_filter_leftright_common_code_all:	
	ld		b,0											;no filter
	ld		a,[shop_card_list]							;first card for all filter will display first the current first card	

shop_filter_leftright_common_code_color:	
	;update card list
	call	populate_shop_card_list
	
	;update	card action
	ld		a,[shop_card_list+3]
	call	print_shop_action
	;print deck
	call	shop_print_deck
	;update	card detail
	ld		a,[shop_card_list+3]
	call	shop_print_card_details_mem


	ret




;moves shop_filter one pos towards right 
shop_move_filter_right:
	ld		hl,shop_filter
	ld		a,3
	cp		[hl]
	jr		z,shop_move_filter_right_reset
	inc		[hl]
	ret
shop_move_filter_right_reset:
	xor		a
	ld		[hl],a
	ret




;moves shop_filter one pos towards left
shop_move_filter_left:
	ld		hl,shop_filter
	xor		a
	cp		[hl]
	jr		z,shop_move_filter_left_reset
	dec		[hl]
	ret
shop_move_filter_left_reset:
	ld		a,3
	ld		[hl],a
	ret



;a = card weight
;return a value
;round ( ((x*64) + (x*32) + (x*4)) / 256 )
;modifies
;	a, hl, de at least
get_card_price:

	;a = weight
	ld		h,0
	ld		l,a
	
	REPEAT	2
			sla		l
			rl		h
	ENDREPEAT
	
	push	hl							;hl = a*4

	REPEAT	3
			sla		l
			rl		h
	ENDREPEAT
										;hl = a*32
	push	hl
	
	sla		l
	rl		h							;hl = a*64
	
	pop		de	
	add		hl,de						;hl = x * 64 + x * 32
	pop		de
	add		hl,de						;hl = hl + x*4
	; now to divide by 256 is shift right hl 8 times .... so , the result is h
	ld		a,h

	ret



;returns d=cards_in_deck , e=cards owned
;modifies a, bc, de, hl
calculate_cards_in_deck_and_owned:
	ld		b,CARD_REG_SIZE+1
	ld		hl,cards_regs+1				;poiting at flags
	ld		d,0
	ld		e,0
calculate_cards_in_deck_loop:
	push	bc
	ld		a,[hl]
	bit		7,a							
	jr		z,calculate_cards_in_deck_loop_not_in_deck
	inc		d							;another one in deck
calculate_cards_in_deck_loop_not_in_deck:	

	bit		6,a
	jr		z,calculate_cards_in_deck_loop_not_owned
	inc		e
calculate_cards_in_deck_loop_not_owned:	

	ld		b,0
	ld		c,CARD_REG_SIZE			
	add		hl,bc						;next record			
	pop		bc
	djnz	calculate_cards_in_deck_loop

	ret




;performs in/out/buy actions at shop
;a card number
;modifies all basic registers
;ret	a=0 couldn't do anything
;		a=1 in
;		a=2 out
;		a=3 bought
shop_action_required:

	call	get_card_address
	inc		hl
	inc		hl
	ld		[tmp_buffer3],hl				;saving hl pointing at card weight

	ld		hl,player_deck_status
	ld		d,0
	ld		e,a
	add		hl,de
	;dec		hl
	push	hl
	
	ld		a,[hl]
	bit		6,a
	jr		z,shop_action_required_buy		;0 => not owned? => try to buy
	bit		7,a
	jr		z,shop_action_required_in		;not in deck -> include in deck
	;in deck -> exclude from deck if number of cards in deck is > PLAYER_MIN_CARDS
	
	IF DEBUG_MODE==0
	push	af
	ld		a,[shop_cards_in_deck]
	cp		PLAYER_MIN_CARDS+1
	jr		c,shop_action_required_in_not_allowed
	jr		shop_action_required_in_allowed
	
shop_action_required_in_not_allowed:
	pop		af
	;TODO: special acction (sound , text, etc). Card cannot be removed from player's deck due to deck would be so small
	xor		a			;ret  coultn't perform action
	jr.		shop_action_required_done
	
shop_action_required_in_allowed:

	pop		af	
	ENDIF

	res		7,a								;removed from deck
	push	af								;update shop_cards_in_deck counter
	ld		a,[shop_cards_in_deck]
	dec		a
	ld		[shop_cards_in_deck],a
	pop		af
	ld		b,2								;ret out done
	jr		shop_action_required_owned_done
shop_action_required_in:
	set		7,a								;in deck
	push	af								;update shop_cards_in_deck counter
	ld		a,[shop_cards_in_deck]
	inc		a
	ld		[shop_cards_in_deck],a
	pop		af	
	ld		b,1								;ret in done
shop_action_required_owned_done:
	push	bc
	
	ld		[hl],a							;done, already in deck
	;update counters
	call	print_shop_counters
	;update deck
	call	shop_print_deck
	;update shop action
	ld		hl,shop_card_list+3
	ld		a,[hl]
	call	print_shop_action	
	
	pop		bc
	ld		a,b								;ret status set
	jr		shop_action_required_done
shop_action_required_buy:
	;money owned is two bytes (no more than 999)
	;money owned hi byte >0 => buy it
	;		else money owned lower byte >= card value => buy it
	;		else buying cancelled
	;
	
	ld		hl,[tmp_buffer3]
	ld		a,[hl]							;a card weight
	call	get_card_price					;a card price
	ld		c,a								;save card price on c
	ld		hl,[shop_coins]					;h higher value
	xor		a
	cp		h	
	jr		z,shop_action_required_money_lowerbyte
	jr		shop_action_required_can_buy
shop_action_required_money_lowerbyte:
	ld		a,c								;get card price from c
	cp		l								;a price  l lower money byte  , a-l
	jr		z,shop_action_required_can_buy
	jr		c,shop_action_required_can_buy
	;we cannot buy this card, not enough money...
	;any special action!!!!					TODO: do something (sound , message ,etc)
	xor		a			;ret  coultn't perform action
	jr		shop_action_required_done
	


shop_action_required_can_buy:
	push	af
	ld		a,[cheat]
	and		a
	jr		z,.continue
	;IF	DEBUG_MODE==1
	ld		c,0							;price always 0
	;ENDIF
.continue:
	pop		af
	; c holds price
	;let's subtract
	ld		d,0
	ld		e,c							;c holds card value
	ld		hl,[shop_coins]

	;ld		a,h
	;ld		h,l
	;ld		l,a

	;ex		de,hl						;hl = de - hl = de - a =  [shop_coins]-price
	and		a							;clear clarry flag
	sbc		hl,de

	;ld		a,h
	;ld		h,l
	;ld		l,a

	ld		[shop_coins],hl
	
	;update flags
	;already owned
	pop		hl
	ld		a,[hl]
	or		64							;owned flag set
	ld		[hl],a
	
	
	;update shop_cards_owned counter
	ld		a,[shop_cards_owned]
	inc		a							;one more
	ld		[shop_cards_owned],a

	
	;update counters
	call	print_shop_counters
	;update deck
	call	shop_print_deck
	;update shop action
	ld		hl,shop_card_list+3
	ld		a,[hl]
	call	print_shop_action	
	
	ld		a,3						;ret it was bought
	
	ret

shop_action_required_done:
	pop		hl

	ret









;a = shop_card_list +0
;b = 0 not filter, b = 1 filter (a card color)
populate_shop_card_list:
	dec		b
	jr		z,populate_shop_card_list_filter

	ld		hl,shop_card_list
	ld		[hl],a							;setting shop_card_list+0
	inc		hl
		
	ld		b,5								;repeat next block 5 times more

populate_shop_card_list_loop:	
	call	populate_shop_card_list_next
	ld		[hl],a							;setting shop_card_list+1 ...5
	inc		hl
	djnz	populate_shop_card_list_loop

	ret


populate_shop_card_list_filter:
	;a holds first filtered card

	ld		hl,shop_card_list
	ld		[hl],a							;setting shop_card_list+0

	ld		b,5								;counter , how many we must find to go

populate_shop_card_list_filter_loop:
	inc		hl
	push	hl
	push	bc
	call	populate_shop_card_list_next_filter
	pop		bc
	pop		hl
	ld		[hl],a
	djnz	populate_shop_card_list_filter_loop		
	
	ret



;a = current card
;return a = next card
populate_shop_card_list_next:
	cp		MAX_CARDS_GAME
	jr		z,populate_shop_card_list_next_equal

	inc		a
	ret

populate_shop_card_list_next_equal:
	xor		a

	ret
	

;a = current card
;return a = previous card
populate_shop_card_list_prev:
	cp		0
	jr		z,populate_shop_card_list_prev_reset
	dec		a						;easy , just the prev card in deck
	ret	

populate_shop_card_list_prev_reset:
	ld		a,MAX_CARDS_GAME		;last one
	ret





	


;a = current card
;return a = next filtered card
;destroy af, b, hl
populate_shop_card_list_next_filter:

	push	af
	call	get_card_address
	inc		hl
	ld		a,[hl]						;card flags on a

	and		0x07						;mask for 3 bits (one of those is set with color flag)
	ld		c,a							;saved on c
	
	;let's look for the next card with same color
populate_shop_card_list_next_filter_loop:
	pop		af							;a = card number
	
	call	populate_shop_card_list_next	
	;a has next card
	push	af
	push	bc							;save mask on c
	call	get_card_address
	pop		bc
	inc		hl
	ld		a,[hl]						;current flag set
	and		0x07						;just interested on color flags
	;let's compare mask on c with a
	and		c							;if it's not the same , zero flag is set
	jr		z,populate_shop_card_list_next_filter_loop
	
	pop		af	

	ret


;a=color (1 brown 2 blue 3 green )
;returns a=card number
;Beware! we should have at least a card of each color in deck
;modifies af,bc,de,hl
search_firstcard_by_color:
	ld		d,0							;first card counter
	cp		1
	jr		z,search_firstcard_by_color_brown
	cp		2
	jr		z,search_firstcard_by_color_blue
	;set green 
	ld		e,0x04
	jr		search_firstcard_by_color_selected
search_firstcard_by_color_brown:
	ld		e,0x01
	jr		search_firstcard_by_color_selected
search_firstcard_by_color_blue:
	ld		e,0x02
search_firstcard_by_color_selected:		
	ld		b,0
	ld		c,CARD_REG_SIZE	
	ld		hl,cards_regs+1				;first flags reg

search_firstcard_by_color_loop:	
	ld		a,[hl]
	and		0x07
	and		e
	jr		nz,search_firstcard_by_color_found
	inc		d
	add		hl,bc						;hl points next flag
	jr		search_firstcard_by_color_loop
	

search_firstcard_by_color_found:
	ld		a,d
	ret




;a = current card
;b = 0 not filtered, 1 filtered
;returns a = previous card
;modifies all basic regs
search_firstcard_backward:
	dec		b
	jr		z,search_firstcard_backward_filtered
	;not filter is needed
	call	populate_shop_card_list_prev
	ret
	
search_firstcard_backward_filtered:
	push	af
	call	get_card_address
	inc		hl
	ld		b,[hl]	
	ld		a,b
	and		0x07
	ld		b,a										;b holds color flags to compare

search_firstcard_backward_filtered_loop:	
	pop		af										
	call	populate_shop_card_list_prev			;next card (without taking into account color)
	push	af
	push	bc
	
	call	get_card_address
	
	pop		bc
	
	inc		hl										;hl pointing at flags mem address
	
	ld		a,[hl]									;flags on a
	and		b										;zero if it's not same color
	jr		z,search_firstcard_backward_filtered_loop
	;found!	, ret a
	
	pop		af										;set stack pointer in right mem address
	ret



;end shop routines




;Modifies all basic registers (af,bc,de,hl)
build_player_deck_for_battle:
	xor		a
	ld		[shop_cards_in_deck],a
	
	ld		b,MAX_CARDS_GAME+1
	ld		c,0
	ld		de,player_cards_deck
	ld		hl,player_deck_status
	
build_player_deck_for_battle_loop:	
	ld		a,[hl]
	bit		7,a
	jr		nz,build_player_deck_for_battle_include
	jr		build_player_deck_for_battle_next
build_player_deck_for_battle_include:
	ld		a,c
	ld		[de],a	
	inc		de
	push	hl												;updates shop_cards_in_deck
	ld		hl,shop_cards_in_deck
	inc		[hl]
	pop		hl
	
build_player_deck_for_battle_next:	
	inc		hl
	inc		c

	
	djnz	build_player_deck_for_battle_loop

	ret

	
	
	
